const isBrowser = () => typeof document !== "undefined";

/**
 * le
 * @param imageUrl
 * @param format
 * @param quality
 * @return  data:image/png;base64,....
 */
async function loadImage(imageUrl, format = "image/png", quality) {
  return new Promise((resolve, reject) => {
    if (typeof document === "undefined") {
      reject();
    }
    const canvas = document.createElement("canvas");
    const context = canvas.getContext("2d");
    const image = new Image();

    image.crossOrigin = "";
    image.onload = function () {
      if (!canvas || !context) {
        reject();
      }
      canvas.height = image.height;
      canvas.width = image.width;
      context.drawImage(image, 0, 0);
      const canvasDataUrl = canvas.toDataURL(format, quality);
      resolve(canvasDataUrl);
    };

    image.onerror = function () {
      reject();
    };

    image.src = imageUrl;
  });
}

// 生成Blob对象
function dataUrlToBlob(dataUrl) {
  if (!isBrowser()) {
    return null;
  }
  const parts = dataUrl.split(",");
  const mimeType = parts[0].match(/:(.*?);/)[1];
  const base64Data = window.atob(parts[1]);
  const length = base64Data.length;
  const uint8Array = new Uint8Array(length);

  for (let i = 0; i < length; i++) {
    uint8Array[i] = base64Data.charCodeAt(i);
  }

  return new Blob([uint8Array], { type: mimeType });
}

/**
 * 通过blob对象 实现下载
 * @param blob
 * @param filename
 * @param mimeType
 * @param target
 */
async function downloadByData(
  blob,
  filename,
  mimeType = "application/octet-stream",
  target = "_blank"
) {
  if (!isBrowser()) {
    return;
  }

  const url = window.URL.createObjectURL(blob);

  const anchor = document.createElement("a");
  anchor.style.display = "none";
  anchor.href = url;
  anchor.setAttribute("download", filename);
  anchor.setAttribute("type", mimeType);

  if (typeof anchor.download !== "undefined") {
    anchor.setAttribute("target", target);
  }

  document.body.appendChild(anchor);
  anchor.click();
  document.body.removeChild(anchor);
  window.URL.revokeObjectURL(url);
}

/**
 *把base64转成blob 在通过blob对象下载文件
 * @param base64
 * @param filename
 */
async function downloadByBase64(base64, filename) {
  //Qe
  const blob = dataUrlToBlob(base64); //Se
  await downloadByData(blob, filename); //Je
}

/**
 *先把图片转成base64
 * @param imageUrl
 * @param filename
 */
async function downloadByOnlineUrl(imageUrl, filename) {
  loadImage(imageUrl).then(base64 => {
    downloadByBase64(base64, filename);
  });
}

/**
 *
 * @param linkUrl
 * @param target
 */
function openLink(linkUrl, target = "_blank") {
  if (!isBrowser()) {
    return;
  }

  const anchor = document.createElement("a");
  anchor.setAttribute("href", linkUrl);
  anchor.setAttribute("target", target);
  anchor.setAttribute("rel", "noreferrer noopener");
  anchor.setAttribute("id", "external");

  const existingAnchor = document.getElementById("external");
  if (existingAnchor) {
    document.body.removeChild(existingAnchor);
  }

  document.body.appendChild(anchor);
  anchor.click();
  anchor.remove();
}

/**
 *根据文件地址下载文件  不只是图片
 * @param fileUrl
 * @param filename
 * @param target
 */
function downloadByUrl(fileUrl, filename, target = "_self") {
  if (!isBrowser()) {
    return;
  }
  const isChrome =
    window.navigator.userAgent.toLowerCase().indexOf("chrome") > -1;
  const isSafari =
    window.navigator.userAgent.toLowerCase().indexOf("safari") > -1;

  if (/(iP)/g.test(window.navigator.userAgent)) {
    console.error("Your browser does not support download!");
    return false;
  }

  if (isChrome || isSafari) {
    const anchor = document.createElement("a");
    anchor.href = fileUrl;
    anchor.target = target;
    if (anchor.download !== undefined) {
      anchor.download =
        filename ||
        fileUrl.substring(fileUrl.lastIndexOf("/") + 1, fileUrl.length);
    }

    if (document.createEvent) {
      const event = document.createEvent("MouseEvents");
      event.initEvent("click", true, true);
      anchor.dispatchEvent(event);
      return true;
    }
  }

  return fileUrl.indexOf("?") === -1
    ? ((fileUrl += "?download"), openLink(fileUrl, target), true)
    : false;
}

export { downloadByOnlineUrl, downloadByBase64, downloadByData, downloadByUrl };
